const { Middleware , EntityScaner } = require("../../springbreeze/lib/index")  ,
    Mongoose = require("mongoose") ,
    Cachegoose = require("cachegoose") ,
    Delegate = require("delegates")

Mongoose.set( "useFindAndModify" , false )
/**
 *  MongoDB 中间件服务
 *      关于Mongoose的学习可参考：https://mongoosejs.com/docs/index.html
 * 
 */
module.exports = class MongoMiddleware extends Middleware {

    constructor(){
        super() 
        this._Model = {}
    }

    before(){

    }

    async start(){
        const app = this 
        //判断是否使用缓存
        if( app.config().cached ) {
            Log.info("开启缓存服务:" , app.config().cached )
            Cachegoose( Mongoose , app.config().cached )
        }
        //详细的Mongoose的连接配置 https://mongoosejs.com/docs/connections.html
        //创建连接,然后执行after加载model
        this.Mongo = Mongoose.createConnection( this.config().uris , this.config().opt )

        //直接暴露Mongo方法
        this.delegate()

        this.Mongo.on("connected" , () => {
            Log.info("Connected by [%s] " , app.opt.uris )
        } )
        this.Mongo.on("disconnected" , err => {
            GetLogger("err").error( "connection error : " , err )
            throw err 
        })
        app.after()
    }

    model( key , opt , tableName ){
        if( !tableName ) tableName = key 
        if( !opt ) return this.Mongo.models[ key ]
        //这里可以给Model增加中间件实现
        return this.Mongo.model( key , opt , tableName )
    }

    delegate(){
        Delegate( this , "Mongo")
            // .method("model")
    }

    after(){
        //加载Models
        this.loadModel()
    }

    loadModel(){
        const path = this.config().modelPath || "model"
        Log.info("开始加载Model,扫描目录：[%s]" , path )
        const modelScaner = new EntityScaner()
        modelScaner.setNextPath( path )
        const models = modelScaner.scan()
        for( let idx in models ){
            const model = models [idx ]
            if( model ) {
                const name = model.name()
                const tableName = model.tableName()
                Log.info("-->加载Schema[%s],绑定表名:[%s],对应文件:[%s]" , name , tableName , model.__path )
                this.model( name , model , tableName )
            }
        }

    }

}